package com.lzw.DailyAudit.service.dateAggregation_02;


import cn.hutool.core.bean.BeanUtil;
import com.hooya.fa.eu.biz.DailyAudit.entity.DailyAuditStatus;
import com.hooya.fa.eu.biz.DailyAudit.entity.MetaStkCustoms;
import com.hooya.fa.eu.biz.DailyAudit.entity.StkOrigDataCollect;
import com.hooya.fa.eu.biz.DailyAudit.entity.dto.B2bDataDTO;
import com.hooya.fa.eu.biz.DailyAudit.mapper.*;
import com.hooya.integrated.common.util.times.DateExtUtil;
import com.xxl.job.core.context.XxlJobHelper;
import lombok.extern.slf4j.Slf4j;
import org.springframework.beans.BeanUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import java.nio.charset.StandardCharsets;
import java.security.MessageDigest;
import java.security.NoSuchAlgorithmException;
import java.time.LocalDate;
import java.time.format.DateTimeFormatter;
import java.time.temporal.ChronoUnit;
import java.util.*;
import java.util.stream.Collectors;
import java.util.stream.Stream;

@Service
@Slf4j
public class Insert_B2B {

	@Autowired
	private DailyProForMaMmMapper dailyProForMaMmMapper;

	@Autowired
	private DailyTempMmjlMapper dailyTempMmjlMapper;

	@Autowired
	private DailyCostHisMapper dailyCostHisMapper;

	@Autowired
	private DailyCostLastMapper dailyCostLastMapper;

	@Autowired
	private DailyMetaStkCustomsMapper dailyMetaStkCustomsMapper;

	@Autowired
	private CommonService commonService;

	@Autowired
	private DailyAuditStatusMapper statusMapper;

	public void insert_b2b(String currentDate) {
		try {

			String name = "insertB2b-02";
			DailyAuditStatus dailyAuditStatus = statusMapper.selectStatus(name, currentDate);
			if (dailyAuditStatus != null && dailyAuditStatus.getFlag() == 1) {
				log.info("{} - 该方法已执行，进行跳过！", name);
				return;
			}

			log.info("开始执行B2B数据插入任务");

			String curMonthFirstDay = DateExtUtil.getCurMonthFirstDay(LocalDate.parse(currentDate, DateTimeFormatter.ofPattern("yyyy-MM-dd")));

			// 查询历史价格数据
			List<B2bDataDTO> hisPriceList = SelectPriceData(currentDate).stream().filter(f->f.getHisPrice()!=null && f.getHisOceanfee()!=null).collect(Collectors.toList()); //fa_eu.temp_mmjl  rxh_europe.cost_his  切换完成
			// 查询最新价格数据
			List<B2bDataDTO> lastPriceList = dailyCostLastMapper.selectLatestPrice().stream().filter(f->f.getLastPrice()!=null && f.getLastOceanfee()!=null).collect(Collectors.toList());// rxh_europe.cost_last  切换完成
			// 获取首次出现日期数据
			List<B2bDataDTO> firstDayData = dailyTempMmjlMapper.selectFirstDayData(curMonthFirstDay, currentDate); // fa_eu.temp_mmjl  -  采用的还是每月的第一天 - 当天    切换完成


			// 获取主要数据
			List<B2bDataDTO> mainData = getMainData(currentDate); // fa_eu.temp_mmjl  rxh_europe.meta_stk_customs  切换完成

			// 添加价格
			List<B2bDataDTO> priceData = addPrice(hisPriceList, lastPriceList, firstDayData);

			//构建海运数据的Map映射集合
			Map<String, List<B2bDataDTO>> oceanFeeDataMap = priceData.stream().collect(Collectors.groupingBy(B2bDataDTO::getCpbh));
			List<B2bDataDTO> mergeData = new ArrayList<>();
			for (B2bDataDTO mainItem : mainData) {
				String key = mainItem.getCpbh();
				if (oceanFeeDataMap.containsKey(key)) {
					List<B2bDataDTO> B2bDataDTOS = oceanFeeDataMap.get(key);
					B2bDataDTOS.forEach(f -> {
						B2bDataDTO newItem = new B2bDataDTO();
						BeanUtils.copyProperties(mainItem, newItem);
						newItem.setPrice(f.getPrice());
						newItem.setOceanfee(f.getOceanfee());
						newItem.setCurrency(f.getCurrency());
						mergeData.add(newItem);
					});
				} else {
					mergeData.add(mainItem);
				}
			}

			List<B2bDataDTO> noPriceData = mergeData.stream().filter(f -> f.getPrice() == null).collect(Collectors.toList());
			if (!noPriceData.isEmpty()) {
				log.error("异常数据共有条数：{}， 异常数据为：{}", noPriceData.size(), noPriceData);
				throw new RuntimeException("异常数据共有条数：" + noPriceData.size() + "， 异常数据为：" + noPriceData);
			}
			mergeData.forEach(f->f.setCurrency("EUR"));

			// 添加ID
			List<B2bDataDTO> addIdData = addId(mergeData, currentDate);
			// 拆分方向
			List<B2bDataDTO> addDirectionData = addDirection(addIdData);
			// 添加发票日期
			List<B2bDataDTO> addInvoiceDateData = addInvoiceDate(addDirectionData, currentDate); //当天时间即可
			// 添加出口价格
			Map<String, Object> exportPriceResult = addExportPrice(addInvoiceDateData, currentDate); //当天的时间  切换完成
			List<B2bDataDTO> withExportPriceData = (List<B2bDataDTO>) exportPriceResult.get("withExportPriceData");
			List<B2bDataDTO> withoutExportPriceData = (List<B2bDataDTO>) exportPriceResult.get("withoutExportPriceData");
			// 添加异常出口价格
			List<B2bDataDTO> abWithExportPriceData = addAbnormalExportPrice(withoutExportPriceData, currentDate); //当天的时间  切换完成

			// 合并所有出口价格数据
			List<B2bDataDTO> allExportPriceData = new ArrayList<>(withExportPriceData);
			allExportPriceData.addAll(abWithExportPriceData);

			Map<String, List<B2bDataDTO>> exportPriceMap = allExportPriceData.stream().collect(Collectors.groupingBy(f -> f.getCpbh() + f.getIndex()));
			List<B2bDataDTO> finalData = new ArrayList<>();
			for (B2bDataDTO mainItem : addInvoiceDateData) {
				String key = mainItem.getCpbh() + mainItem.getIndex();
				if (exportPriceMap.containsKey(key)) {
					for (B2bDataDTO exportPriceItem : exportPriceMap.get(key)) {
						B2bDataDTO mergedItem = new B2bDataDTO();
						BeanUtil.copyProperties(mainItem, mergedItem);
						mergedItem.setExportprice(exportPriceItem.getExportprice());
						finalData.add(mergedItem);
					}
				} else {
					finalData.add(mainItem);
				}
			}

			// 处理转运类型的数据
			String formattedDate = LocalDate.parse(currentDate, DateTimeFormatter.ofPattern("yyyy-MM-dd")).format(DateTimeFormatter.ofPattern("yyyyMM"));

			finalData.stream().filter(data -> "转运".equals(data.getType())).forEach(data -> {
				data.setOceanfee(0.0);
				data.setExportprice(0.0);
				data.setInvoiceno("BTOB-" + formattedDate);
				data.setStax(null);
				data.setBtax(null);
			});

			// 数据验证
			commonService.dataVerificationB2b(finalData);

			// 转换为实体类并保存
			List<StkOrigDataCollect> records = commonService.convertB2bToStkOrigDataCollect(finalData);

			commonService.batchInsert(records); // fa_eu_daily.stk_origData_collect

			// 修改执行状态
			commonService.UpdateOrInsertStatus(dailyAuditStatus, name, currentDate);

			log.info("B2B数据处理完成，共处理{}条记录", records.size());
			XxlJobHelper.log("B2B数据处理完成，共处理{}条记录", records.size());
		} catch (Exception e) {
			log.error("处理B2B数据失败", e);
			XxlJobHelper.log("处理B2B数据失败");
			throw new RuntimeException("处理B2B数据失败", e);
		}
	}

	private List<B2bDataDTO> SelectPriceData(String currentDate) {
		List<B2bDataDTO> result = new ArrayList<>();
		List<String> cpbhList = new ArrayList<>();
		List<B2bDataDTO> CurMMJLData = dailyCostHisMapper.selectMMjlDataByCurrentDate(currentDate); // 查询当天的mmjl
		CurMMJLData.forEach(f->cpbhList.add(f.getCpbh()));
		List<B2bDataDTO> CostHisData = dailyCostHisMapper.selectCostHisDataByCurrentDate(cpbhList);  // 查询历史数据
		for (B2bDataDTO MMJLData : CurMMJLData) {
			String cpbh = MMJLData.getCpbh();
			String date = MMJLData.getDate();
			for (B2bDataDTO costHisData : CostHisData) {
				String beginDt = costHisData.getBeginDt();
				String endDt = costHisData.getEndDt();
				if (cpbh.equals(costHisData.getCpbh()) && date.compareTo(beginDt) >= 0 && date.compareTo(endDt) <= 0) {
					B2bDataDTO b2bDataDTO = new B2bDataDTO();
					BeanUtil.copyProperties(MMJLData, b2bDataDTO);
					b2bDataDTO.setHisPrice(costHisData.getHisPrice());
					b2bDataDTO.setHisOceanfee(costHisData.getHisOceanfee());
					b2bDataDTO.setSort(costHisData.getSort());
					b2bDataDTO.setBeginDt(costHisData.getBeginDt());
					b2bDataDTO.setEndDt(costHisData.getEndDt());
					result.add(b2bDataDTO);
				}
			}

		}
		return result;
	}

	/**
	 * 获取主要数据
	 */
	private List<B2bDataDTO> getMainData(String currentDate) {
		// 查询temp_mmjl表数据（包含仓库信息）
		List<B2bDataDTO> tempMmjlList = dailyTempMmjlMapper.selectList(currentDate); //fa_eu.temp_mmjl a, fa_eu.meta_warehouse b  切换完成
		// 添加税号头信息
		addTaxIdHeader(tempMmjlList);

		// 添加形式转的买卖记录
		List<B2bDataDTO> proFormaMm = addProFormaMm(currentDate, tempMmjlList); // fa_eu.daily_proForma_mm a, fa_eu.meta_warehouse b  切换完成
		addTaxIdHeader(proFormaMm);

		// 合并形式转数据
		tempMmjlList.addAll(proFormaMm);
		// 处理买家逻辑
		tempMmjlList.forEach(data -> {
			String buyer = getBuyer(data.getBuyer(), data.getBuyertaxid());
			data.setBuyer(buyer);

			// 设置其他属性
			data.setFromcompany(data.getSeller());
			data.setTocompany(data.getBuyer());
			data.setStax(data.getSellertaxid());
			data.setBtax(data.getBuyertaxid());
		});

		log.info("获取主要数据成功，数据条数：{}", tempMmjlList.size());
		return tempMmjlList;
	}

	/**
	 * 添加税号头信息
	 */
	private void addTaxIdHeader(List<B2bDataDTO> dataList) {
		for (B2bDataDTO data : dataList) {
			// 根据业务逻辑设置税号信息
			if (data.getFromcountry() != null) {
				data.setSellertaxid(data.getFromcountry());
			}

			// 买家税号：收货地除DE，PL，IT，ES外均使用FR
			if (data.getTocountry() != null) {
				if ("DE".equals(data.getTocountry()) || "PL".equals(data.getTocountry()) || "IT".equals(data.getTocountry()) || "ES".equals(data.getTocountry())) {
					data.setBuyertaxid(data.getTocountry());
				} else {
					data.setBuyertaxid("FR");
				}
			}

			// 无ES税号的公司，改为FR
			if ("ES".equals(data.getTocountry()) && data.getBuyer() != null) {
				if ("kerui".equals(data.getBuyer()) || "giantex".equals(data.getBuyer())) {
					data.setBuyertaxid("FR");
				}
			}

			// 202510 CZ税号使用
			if ("CZ".equals(data.getTocountry()) && data.getBuyer() != null) {
				if ("lifezeal".equals(data.getBuyer()) || "komfort".equals(data.getBuyer())) {
					data.setBuyertaxid("CZ");
				}
			}

			// 特殊公司
			if (data.getBuyer() != null) {
				if ("mingdun".equals(data.getBuyer())) {
					data.setBuyertaxid("FR");
				} else if ("itsrlcostway".equals(data.getBuyer())) {
					data.setBuyertaxid("IT");
				}
			}
		}
	}

	/**
	 * 添加形式转的买卖记录
	 */
	private List<B2bDataDTO> addProFormaMm(String currentDate, List<B2bDataDTO> mainData) {
		List<B2bDataDTO> result = new ArrayList<>();

		List<B2bDataDTO> proForMaMmList = dailyProForMaMmMapper.getProForMaMm(currentDate); // fa_eu.temp_mmjl mm, fa_eu.temp_xsjl xs,fa_eu.meta_warehouse mw

		// 创建一个以sheetnumber为键的映射，存储mainData中的buyer和buyertaxid
		Map<String, B2bDataDTO> mainDataMap = mainData.stream().filter(data -> data.getSheetnumber() != null).collect(Collectors.toMap(B2bDataDTO::getSheetnumber, data -> data, (existing, replacement) -> existing));

		// 为proForMaMmList中的每条记录设置buyer和buyertaxid
		for (B2bDataDTO proFormaRecord : proForMaMmList) {
			String sheetnumber = proFormaRecord.getSheetnumber();
			if (sheetnumber != null && mainDataMap.containsKey(sheetnumber)) {
				B2bDataDTO mainRecord = mainDataMap.get(sheetnumber);
				proFormaRecord.setBuyer(mainRecord.getBuyer());
				proFormaRecord.setBuyertaxid(mainRecord.getBuyertaxid());
				proFormaRecord.setFromcountry(proFormaRecord.getBuyertaxid() != null ? proFormaRecord.getBuyertaxid() : "");

				// 设置seller为getBuyer(buyer, buyertaxid)的结果
				String seller = getBuyer(proFormaRecord.getBuyer(), proFormaRecord.getBuyertaxid());
				proFormaRecord.setSeller(seller);

				// 在Java中，我们不需要实际删除字段，只需要将它们设为null
				proFormaRecord.setBuyer(null);
				proFormaRecord.setBuyertaxid(null);

				proFormaRecord.setBuyer(proFormaRecord.getBuyermm());
				proFormaRecord.setBuyermm(null);

				if (shouldIncludeProFormaRecord(proFormaRecord)) {
					// 在Java中，我们将这些字段设为null
					proFormaRecord.setMmTocountry(null);
					proFormaRecord.setXsBelongs(null);

					result.add(proFormaRecord);
				}
			}
		}

		return result;
	}


	/**
	 * 处理买家逻辑
	 */
	private String getBuyer(String tocompany, String buyertaxid) {
		// 针对fds、costway,拼接的国家为买方国家
		String tocountry = (buyertaxid != null) ? buyertaxid.toLowerCase() : "";

		if ("fds".equals(tocompany)) {
			return "fds-" + tocountry;
		} else if ("costway".equals(tocompany)) {
			return "costway-" + tocountry;
		} else {
			return tocompany;
		}
	}

	/**
	 * 添加价格
	 */
	private List<B2bDataDTO> addPrice(List<B2bDataDTO> hisPrice, List<B2bDataDTO> lastPrice, List<B2bDataDTO> firstDay) {
		// 构建历史价格映射，按sort字段排序并按cpbh分组，取每组第一条记录
		Map<String, B2bDataDTO> withHisPriceMap = hisPrice.stream()
				.sorted(Comparator.comparing(B2bDataDTO::getSort))
				.collect(Collectors.groupingBy(
						B2bDataDTO::getCpbh,
						Collectors.collectingAndThen(
								Collectors.toList(),
								list -> list.get(0)
						)
				));

		//设置得到日期的第一个数据并设置参数
		List<B2bDataDTO> withHisPrice = new ArrayList<>(withHisPriceMap.values()).stream().peek(f -> {
			f.setPrice(f.getHisPrice());
			f.setOceanfee(f.getHisOceanfee());
		}).collect(Collectors.toList());

		//得到不重复的cpbh数据
		List<B2bDataDTO> withoutPriceData = mergeAndGetDoNotRepeatCpbh(firstDay, withHisPrice);

		Map<String, List<B2bDataDTO>> lastPriceMap = lastPrice.stream().collect(Collectors.groupingBy(B2bDataDTO::getCpbh));
		List<B2bDataDTO> addLastPrice = new ArrayList<>();
		for (B2bDataDTO mainItem : withoutPriceData) {
			String key = mainItem.getCpbh();
			if (lastPriceMap.containsKey(key)) {
				List<B2bDataDTO> B2bDataDTOS = lastPriceMap.get(key);
				B2bDataDTOS.forEach(f -> {
					B2bDataDTO newItem = new B2bDataDTO();
					BeanUtils.copyProperties(mainItem, newItem);
					newItem.setLastPrice(f.getLastPrice());
					newItem.setLastOceanfee(f.getLastOceanfee());
					addLastPrice.add(newItem);
				});
			} else {
				addLastPrice.add(mainItem);
			}
		}
		addLastPrice.forEach(f -> {
			f.setPrice(f.getLastPrice());
			f.setOceanfee(f.getLastOceanfee());
		});

		return Stream.concat(withHisPrice.stream(), addLastPrice.stream())
				.collect(Collectors.toList());
	}

	// 合并并获取不重复的cpbh数据
	private static List<B2bDataDTO> mergeAndGetDoNotRepeatCpbh(List<B2bDataDTO> firstDay, List<B2bDataDTO> withHisPrice) {
		// 1. 合并 withHisPrice 和 firstDay 两个集合
		List<B2bDataDTO> combined = Stream.concat(withHisPrice.stream(), firstDay.stream())
				.collect(Collectors.toList());

		// 2. 统计每个 cpbh 在合并后的总出现次数
		Map<String, Long> cpbhCount = combined.stream()
				.map(B2bDataDTO::getCpbh)
				.collect(Collectors.groupingBy(
						cpbh -> cpbh,  // 按 cpbh 分组
						Collectors.counting()  // 统计每个分组的数量
				));

		// 3. 筛选出仅出现一次的 cpbh 对应的记录（即两个集合中均不重复的记录）
		return combined.stream()
				.filter(dto -> cpbhCount.get(dto.getCpbh()) == 1)  // 只保留出现次数为1的记录
				.collect(Collectors.toList());
	}

	/**
	 * 添加ID
	 */
	private List<B2bDataDTO> addId(List<B2bDataDTO> data, String date) {
		List<B2bDataDTO> idData = data.stream()
				.map(item -> {
					B2bDataDTO newItem = new B2bDataDTO();
					BeanUtils.copyProperties(item, newItem);
					return newItem;
				})
				.collect(Collectors.toList());

		// 区分转运和非转运数据
		List<B2bDataDTO> proFormaData = idData.stream()
				.filter(item -> "转运".equals(item.getType()))
				.map(item -> {
					// 为转运数据创建副本
					B2bDataDTO newItem = new B2bDataDTO();
					BeanUtils.copyProperties(item, newItem);
					return newItem;
				})
				.collect(Collectors.toList());

		idData = idData.stream()
				.filter(item -> !"转运".equals(item.getType()))
				.collect(Collectors.toList());

		List<B2bDataDTO> result = new ArrayList<>();

		// 处理转运数据
		for (B2bDataDTO item : proFormaData) {
			// 对买卖转销售记录增加inoutDate区分，确保发票id唯一性
			item.set_idString(date + item.getDate() + item.getSeller() + item.getBuyer() + item.getFromcountry() + item.getSellertaxid() + item.getBuyertaxid());
			calculateAndSetId(item);
			result.add(item);
		}

		// 处理非转运数据
		for (B2bDataDTO item : idData) {
			item.set_idString(date + item.getSeller() + item.getBuyer() + item.getFromcountry() + item.getSellertaxid() + item.getBuyertaxid());
			calculateAndSetId(item);
			result.add(item);
		}

		return result;
	}

	/**
	 * 计算并设置ID
	 */
	private void calculateAndSetId(B2bDataDTO item) {
		try {
			MessageDigest md = MessageDigest.getInstance("MD5");
			byte[] hashBytes = md.digest(item.get_idString().getBytes(StandardCharsets.UTF_8));
			StringBuilder sb = new StringBuilder();
			for (byte b : hashBytes) {
				sb.append(String.format("%02x", b));
			}
			item.set_id(sb.toString());
		} catch (NoSuchAlgorithmException e) {
			log.error("计算MD5哈希失败", e);
		}
	}

	/**
	 * 添加方向
	 */
	private List<B2bDataDTO> addDirection(List<B2bDataDTO> data) {
		List<B2bDataDTO> result = new ArrayList<>();

		// 添加进口数据
		for (B2bDataDTO item : data) {
			B2bDataDTO inItem = new B2bDataDTO();
			BeanUtil.copyProperties(item, inItem);
			inItem.setBelongs(item.getBuyer());
			inItem.setDirection("in");
			result.add(inItem);
		}

		// 添加出口数据
		for (B2bDataDTO item : data) {
			B2bDataDTO outItem = new B2bDataDTO();
			BeanUtil.copyProperties(item, outItem);
			outItem.setBelongs(item.getSeller());
			outItem.setDirection("out");
			result.add(outItem);
		}

		return result;
	}

	/**
	 * 添加发票日期
	 */
	private List<B2bDataDTO> addInvoiceDate(List<B2bDataDTO> data, String end) {
		List<B2bDataDTO> result = new ArrayList<>();

		// 对于中国船公司这一块业务逻辑不再需要 -- 所有的数据 -- 日期都默认为当月的最后一天 -- 月审计逻辑
//        // 获取中国公司列表
//        List<String> chinaCorpList = metaCorpHeaderMapper.selectChinaCorpList();
//
//        // 计算两个日期
//        LocalDate nextFirst;
//        LocalDate currLast;
//        try {
//            DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
//            nextFirst = LocalDate.parse(end, formatter);  // 09-01
//            currLast = nextFirst.minusDays(1);  // 08-31
//        } catch (Exception e) {
//            log.error("解析日期失败", e);
//            return result;
//        }
//
//        for (B2bDataDTO item : data) {
//            // 根据是否为中国公司设置不同的发票日期
//            try {
//                String tocompany = item.getBuyer();
//                boolean isChinaCorp = false;
//
//                if (tocompany != null && !tocompany.isEmpty()) {
//                    // 提取tocompany中"-"前的部分
//                    String tocompanyPrefix = tocompany.split("-")[0];
//                    // 判断是否在中国公司列表中
//                    isChinaCorp = chinaCorpList.contains(tocompanyPrefix);
//                }
//
//                // 如果是到中国公司的，使用nextFirst(2025-09-01)日期，否则使用currLast日期(2025-08-31)
//                LocalDate invoiceDate = isChinaCorp ? nextFirst : currLast;
//                item.setInvoicedate(java.sql.Date.valueOf(invoiceDate));
//            } catch (Exception e) {
//                log.error("设置发票日期失败", e);
//            }
//
//            result.add(item);
//        }

		DateTimeFormatter formatter = DateTimeFormatter.ofPattern("yyyy-MM-dd");
		LocalDate invoiceDate = LocalDate.parse(end, formatter);
		data.forEach(f -> {
			f.setInvoicedate(String.valueOf(invoiceDate));
			f.setIndex(f.getSheetnumber() + "|" + f.getDirection()); // 更新索引  --  所谓索引不过是判断一条信息的唯一值罢了
			result.add(f);
		});

		log.info("添加发票日期成功，数据条数：{}", result.size());

		return result;
	}

	private List<B2bDataDTO> exportPriceDataToB2bDataDTO() {
		// 查询出口价格数据
		List<MetaStkCustoms> exportPriceDataList = dailyMetaStkCustomsMapper.selectList(); // fa_eu.meta_stk_customs
		// 过滤掉exportprice为空的记录，并转换为B2bDataDTO格式
		return exportPriceDataList.stream().filter(item -> item.getExportPrice() != null) // exportprice不为空
				.map(item -> {
					B2bDataDTO dto = new B2bDataDTO();
					dto.setCpbh(item.getCpbh() != null ? item.getCpbh().toUpperCase() : null);
					dto.setExportprice(item.getExportPrice());
					dto.setQty(item.getQty() != null ? item.getQty() : 0);
					// 设置价格归属公司（根据belongs字段处理）
					dto.setBelongs(item.getPriceBelongs());
					dto.setExportpricedate(item.getExportPriceDate());
					return dto;
				}).collect(Collectors.toList());
	}

	/**
	 * 添加出口价格
	 */
	private Map<String, Object> addExportPrice(List<B2bDataDTO> mainData, String priceDate) {
		Map<String, Object> result = new HashMap<>();

		try {
			List<B2bDataDTO> exportPriceData = exportPriceDataToB2bDataDTO();  //  切换完成

			// 创建一个映射，键为cpbh+pricebelongs，值为匹配的exportPrice记录列表
			Map<String, List<B2bDataDTO>> exportPriceDataMap = exportPriceData.stream().collect(Collectors.groupingBy(f -> f.getCpbh() + f.getBelongs()));
			List<B2bDataDTO> mergeData = new ArrayList<>();
			for (B2bDataDTO mainItem : mainData) {
				String key = mainItem.getCpbh() + mainItem.getAbbrbelongs();
				if (exportPriceDataMap.containsKey(key)) {
					for (B2bDataDTO exportPriceItem : exportPriceDataMap.get(key)) {
						B2bDataDTO mergedItem = new B2bDataDTO();
						BeanUtil.copyProperties(mainItem, mergedItem);
						mergedItem.setExportprice(exportPriceItem.getExportprice());
						mergedItem.setExportpricedate(exportPriceItem.getExportpricedate());
						mergedItem.setQty(exportPriceItem.getQty());
						mergeData.add(mergedItem);
					}
				} else {
					mergeData.add(mainItem);
				}
			}


			// 分离有出口价格和无出口价格的数据
			Map<String, B2bDataDTO> WithExportPriceData = dealMergeData(priceDate, mergeData);
			List<B2bDataDTO> withoutExportPriceData = mainData.stream().filter(item -> !WithExportPriceData.containsKey(item.getCpbh() + item.getSheetnumber() + item.getDirection())).collect(Collectors.toList());

			result.put("withExportPriceData", new ArrayList<>(WithExportPriceData.values()));
			result.put("withoutExportPriceData", withoutExportPriceData);

			log.info("添加出口价格成功，有出口价格数据条数：{}，无出口价格数据条数：{}", WithExportPriceData.size(), withoutExportPriceData.size());

			return result;
		} catch (Exception e) {
			log.error("添加出口价格失败", e);
			throw new RuntimeException("添加出口价格失败", e);
		}
	}

	/**
	 * 添加异常出口价格
	 */
	private List<B2bDataDTO> addAbnormalExportPrice(List<B2bDataDTO> nopriceData, String priceDate) {
		try {
			// 查询出口价格数据
			List<B2bDataDTO> exportPriceData = exportPriceDataToB2bDataDTO();

			// 创建一个映射，键为cpbh+pricebelongs，值为匹配的exportPrice记录列表
			Map<String, List<B2bDataDTO>> exportPriceDataMap = exportPriceData.stream().collect(Collectors.groupingBy(B2bDataDTO::getCpbh));

			// 执行类似pandas merge的左连接操作
			List<B2bDataDTO> mergeData = new ArrayList<>();
			for (B2bDataDTO mainItem : nopriceData) {
				String key = mainItem.getCpbh();
				if (exportPriceDataMap.containsKey(key)) {
					for (B2bDataDTO exportPriceItem : exportPriceDataMap.get(key)) {
						B2bDataDTO mergedItem = new B2bDataDTO();
						BeanUtil.copyProperties(mainItem, mergedItem);
						mergedItem.setExportprice(exportPriceItem.getExportprice());
						mergedItem.setExportpricedate(exportPriceItem.getExportpricedate());
						mergedItem.setQty(exportPriceItem.getQty());
						mergeData.add(mergedItem);
					}
				} else {
					mergeData.add(mainItem);
				}
			}

			//处理后续的mergeData数据
			Map<String, B2bDataDTO> WithExportPriceData = dealMergeData(priceDate, mergeData);

			log.info("添加异常出口价格成功，数据条数：{}", WithExportPriceData.values().size());

			return new ArrayList<>(WithExportPriceData.values());

		} catch (Exception e) {
			log.error("添加异常出口价格失败", e);
			throw new RuntimeException("添加异常出口价格失败", e);
		}
	}

	/**
	 * 处理合并后的数据
	 */
	private static Map<String, B2bDataDTO> dealMergeData(String priceDate, List<B2bDataDTO> mergeData) {
		// 分离有出口价格和无出口价格的数据
		List<B2bDataDTO> withExportPriceData = mergeData.stream().filter(item -> item.getExportprice() != null).collect(Collectors.toList());

		// 计算日期差并过滤
		LocalDate priceLocalDate = LocalDate.parse(priceDate);
		List<B2bDataDTO> withValidDateDiff = new ArrayList<>();
		// date_differ>0的数据
		for (B2bDataDTO item : withExportPriceData) {
			if (item.getExportpricedate() != null) {
				try {
					LocalDate exportPriceDate = LocalDate.parse(item.getExportpricedate());
					long dateDiff = ChronoUnit.DAYS.between(exportPriceDate, priceLocalDate);

					// 排除endDate后的数据（date_differ > 0）
					if (dateDiff > 0) {
						item.setDateDiffer(dateDiff); // 使用dateDiffer字段存储日期差
						withValidDateDiff.add(item);
					}
				} catch (Exception e) {
					log.warn("日期解析失败: {}", item.getExportpricedate());
				}
			}
		}

		// 按照日期差、数量qty、出口价格排序，然后按cpbh和index(sheetNumber+direction)分组，取每组第一条记录
		Map<String, List<B2bDataDTO>> groupedData = withValidDateDiff.stream().sorted(Comparator.comparing(B2bDataDTO::getDateDiffer).thenComparing(B2bDataDTO::getQty, Comparator.nullsLast(Comparator.reverseOrder())).thenComparing(B2bDataDTO::getExportprice, Comparator.nullsLast(Comparator.reverseOrder()))).collect(Collectors.groupingBy(f -> f.getCpbh() + f.getSheetnumber() + f.getDirection()));

		// 取每组第一条记录
		Map<String, B2bDataDTO> WithExportPriceData = new HashMap<>();
		for (String key : groupedData.keySet()) {
			List<B2bDataDTO> group = groupedData.get(key);
			if (!WithExportPriceData.containsKey(key) && !group.isEmpty()) {
				WithExportPriceData.put(key, group.get(0));
			}
		}
		return WithExportPriceData;
	}

	/**
	 * 判断proForma记录是否应该包含在结果中
	 * 对应Python中的query筛选逻辑
	 */
	private boolean shouldIncludeProFormaRecord(B2bDataDTO record) {
		String seller = record.getSeller();
		String xsBelongs = record.getXsBelongs();
		String fromCountry = record.getFromcountry();
		String mmToCountry = record.getMmTocountry();

		// 检查seller是否以'costway'或'fds'开头
		boolean sellerStartsWithCostwayOrFds = (seller != null) && (seller.startsWith("costway") || seller.startsWith("fds"));

		// 检查xsBelongs是否以'costway'或'fds'开头
		boolean xsBelongsStartsWithCostwayOrFds = (xsBelongs != null) && (xsBelongs.startsWith("costway") || xsBelongs.startsWith("fds"));

		// 前两个条件必须同时满足
		boolean firstCondition = sellerStartsWithCostwayOrFds && xsBelongsStartsWithCostwayOrFds;

		if (!firstCondition) {
			return false;
		}

		// 检查fromcountry != mmTocountry
		boolean countriesNotEqual = !Objects.equals(fromCountry, mmToCountry);

		if (countriesNotEqual) {
			return true;
		}

		// 如果fromcountry == mmTocountry，则需要满足额外条件
		// seller != xsBelongs
		boolean sellerNotEqualsXsBelongs = !Objects.equals(seller, xsBelongs);

		if (!sellerNotEqualsXsBelongs) {
			return false;
		}

		// ~(seller.str.startswith('fds') and xs_belongs.str.startswith('fds'))
		// 即seller和xs_belongs不能都以'fds'开头
		boolean bothStartWithFds = seller.startsWith("fds") && xsBelongs.startsWith("fds");

		return !bothStartWithFds;
	}
}